/*
 * Created by IntelliJ IDEA.
 * User: amrk
 * Date: 5/12/2004
 * Time: 19:48:49
 */
package com.talios.jira.idea;

import com.intellij.openapi.diagnostic.Logger;
import com.intellij.openapi.util.InvalidDataException;
import com.intellij.openapi.util.JDOMExternalizable;
import com.intellij.openapi.util.WriteExternalException;
import com.talios.jira.browser.ColumnMetaInfo;
import com.talios.jira.browser.ColumnSetting;
import com.talios.jira.browser.signals.JiraServerDetails;
import org.jdom.Element;

import java.util.ArrayList;
import java.util.Collections;
import java.util.Comparator;
import java.util.List;

public class JiraConfiguration implements JDOMExternalizable {
    private static final Logger LOGGER = Logger.getInstance("Jira Browser");

    private boolean enableIssueTracking;
    private boolean autoRefresh;
    private boolean useExternalBrowser;
    private int refreshTimeout;
    private boolean annotateIssues;
    private List<JiraServerDetails> serverList = new ArrayList<JiraServerDetails>();
    private List columnList = new ArrayList();

    public boolean getEnableIssueTracking() {
        return enableIssueTracking;
    }

    public void setEnableIssueTracking(boolean enableIssueTracking) {
        this.enableIssueTracking = enableIssueTracking;
    }

    public boolean getAutoRefresh() {
        return autoRefresh;
    }

    public void setAutoRefresh(boolean autoRefresh) {
        this.autoRefresh = autoRefresh;
    }

    public boolean getUseExternalBrowser() {
        return useExternalBrowser;
    }

    public void setUseExternalBrowser(boolean useExternalBrowser) {
        this.useExternalBrowser = useExternalBrowser;
    }

    public int getRefreshTimeout() {
        return refreshTimeout;
    }

    public void setRefreshTimeout(int refreshTimeout) {
        this.refreshTimeout = refreshTimeout;
    }

    public boolean getAnnotateIssues() {
        return annotateIssues;
    }

    public void setAnnotateIssues(boolean annotateIssues) {
        this.annotateIssues = annotateIssues;
    }

    public List<JiraServerDetails> getServerList() {
        return serverList;
    }

    public void setServerList(List<JiraServerDetails> serverList) {
        this.serverList = serverList;
    }

    public List getColumnList() {
        return columnList;
    }

    public void setColumnList(List columnList) {
        this.columnList = columnList;
    }

    public void writeExternal(Element element) throws WriteExternalException {
        element.setAttribute("enableIssueTracking", Boolean.valueOf(enableIssueTracking).toString());
        element.setAttribute("autoRefresh", Boolean.valueOf(autoRefresh).toString());

        element.setAttribute("useExternalBrowser", Boolean.valueOf(useExternalBrowser).toString());
        element.setAttribute("refreshTimeout", Integer.toString(refreshTimeout));

        element.setAttribute("annotateissues", Boolean.valueOf(annotateIssues).toString());

        // Store server configuration
        Element serversElement = element.getChild("servers");
        if (serversElement == null) {
            serversElement = new Element("servers");
            element.addContent(serversElement);
        }

        // Remove any existing configurations
        serversElement.removeChildren("server");

        // Write out servers
        for (Object o : getServerList()) {
            JiraServerDetails jiraServerDetails = (JiraServerDetails) o;
            Element serverDetail = new Element("server");
            jiraServerDetails.writeExternal(serverDetail);
            serversElement.addContent(serverDetail);
        }

        // Store column configuration
        Element columnsElement = element.getChild("columns");
        if (columnsElement == null) {
            columnsElement = new Element("columns");
            element.addContent(columnsElement);
        }

        // Remove any existing column settings
        columnsElement.removeChildren("column");

        // Write out columns
        for (Object o1 : getColumnList()) {
            ColumnSetting columnSetting = (ColumnSetting) o1;
            Element column = new Element("column");
            columnSetting.writeExternal(column);
            columnsElement.addContent(column);
        }

    }

    public void readExternal(Element element) throws InvalidDataException {
        // TODO: Check nulls for new project and set default values
        try {
            setEnableIssueTracking(Boolean.valueOf(JDomSupport.getAttributeWithDefault(element, "enableIssueTracking", "false")));
            setAutoRefresh(Boolean.valueOf(JDomSupport.getAttributeWithDefault(element, "autoRefresh", "false")));
            setUseExternalBrowser(Boolean.valueOf(JDomSupport.getAttributeWithDefault(element, "useExternalBrowser", "false")));
            setRefreshTimeout(Integer.parseInt(JDomSupport.getAttributeWithDefault(element, "refreshTimeout", "60")));
            setAnnotateIssues(Boolean.valueOf(JDomSupport.getAttributeWithDefault(element, "annotateissues", "false")));

            JiraServerDetails tempServer = new JiraServerDetails();
            tempServer.readExternal(element);

            // Load Configured Servers
            Element serversElement = element.getChild("servers");
            if (serversElement != null) {
                List<? extends Object> serverList = serversElement.getChildren("server");
                for (Object aServerList : serverList) {
                    Element serverElement = (Element) aServerList;
                    JiraServerDetails serverDetail = new JiraServerDetails();
                    serverDetail.readExternal(serverElement);
                    getServerList().add(serverDetail);
                }
            }

            // Load Configured Columns
            Element columnsElement = element.getChild("columns");
            if (columnsElement != null) {
                List<? extends Object> columnList = columnsElement.getChildren("column");
                if (columnList.isEmpty()) {
                    getColumnList().addAll(ColumnMetaInfo.getDefaultColumnSettings());
                } else {
                    for (Object aColumnList : columnList) {
                        Element columnElement = (Element) aColumnList;
                        ColumnSetting columnDetail = new ColumnSetting();
                        columnDetail.readExternal(columnElement);
                        getColumnList().add(columnDetail);
                    }
                }
            } else {
                getColumnList().addAll(ColumnMetaInfo.getDefaultColumnSettings());
            }

            Collections.sort(columnList, new Comparator() {
                public int compare(Object o1, Object o2) {
                    ColumnSetting c1 = (ColumnSetting) o1;
                    ColumnSetting c2 = (ColumnSetting) o2;
                    return c1.getPosition().compareTo(c2.getPosition());
                }
            });

        } catch (NullPointerException e) {
            LOGGER.error("Error reading properties: " + e.getMessage(), e);
        }

    }
}
